package com.oystertech.sportcms.common.util;

import cn.hutool.core.codec.Base64;
import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.convert.Convert;
import cn.hutool.core.util.StrUtil;
import cn.hutool.crypto.symmetric.AES;
import com.oystertech.sportcms.common.constant.SecurityConstants;
import com.oystertech.sportcms.common.constant.SystemConstants;
import com.oystertech.sportcms.security.userdetails.SysUserDetails;
import org.springframework.security.core.Authentication;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.util.PatternMatchUtils;

import java.util.Collection;
import java.util.Collections;
import java.util.Objects;
import java.util.Set;
import java.util.stream.Collectors;

public class SecurityUtils {
	/**
	 * 获取当前登录人信息
	 *
	 * @return
	 */
	public static SysUserDetails getUser() {
		Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
		if (authentication != null) {
			Object principal = authentication.getPrincipal();
			if (principal instanceof SysUserDetails) {
				return (SysUserDetails) authentication.getPrincipal();
			}
		}
		return null;
	}

	/**
	 * 获取用户ID
	 *
	 * @return Long
	 */
	public static Long getUserId() {
		return Convert.toLong(Objects.requireNonNull(getUser()).getUserId());
	}

	/**
	 * 获取用户角色集合
	 *
	 * @return Set<String>
	 */
	public static Set<String> getRoles() {
		Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
		if (authentication != null) {
			Collection<? extends GrantedAuthority> authorities = authentication.getAuthorities();
			if (CollectionUtil.isNotEmpty(authorities)) {
				return authorities.stream().filter(item -> item.getAuthority().startsWith("ROLE_"))
						.map(item -> StrUtil.removePrefix(item.getAuthority(), "ROLE_"))
						.collect(Collectors.toSet());
			}
		}
		return Collections.EMPTY_SET;
	}

	/**
	 * 获取用户权限集合
	 *
	 * @return Set<String>
	 */
	public static Set<String> getPerms() {
		Authentication authentication = SecurityContextHolder.getContext().getAuthentication();
		if (authentication != null) {
			Collection<? extends GrantedAuthority> authorities = authentication.getAuthorities();
			if (CollectionUtil.isNotEmpty(authorities)) {
				return authorities.stream().map(GrantedAuthority::getAuthority)
						.filter(authority -> !authority.startsWith("ROLE_"))
						.collect(Collectors.toSet());
			}
		}
		return Collections.EMPTY_SET;
	}

	/**
	 * 是否超级管理员
	 * 超级管理员忽视任何权限判断
	 *
	 * @return boolean
	 */
	public static boolean isRoot() {
		return getRoles().contains(SystemConstants.ROOT_ROLE_CODE);
	}

	/**
	 * 是否拥有权限判断
	 * 适用业务判断(接口权限判断适用Spring Security 自带注解 PreAuthorize 判断即可 )
	 *
	 * @return boolean
	 */
	public static boolean hasPerm(String perm) {

		if (isRoot()) return true;

		Set<String> perms = getPerms();

		return perms.stream().anyMatch(item -> PatternMatchUtils.simpleMatch(perm, item));
	}

	/**
	 * 证件号加密
	 *
	 * @param idCardType 证件号类型
	 * @param idCard     证件号明文
	 * @return String 证件号密文
	 */
	public static String idCardEncrypt(int idCardType, String idCard) {
		if (idCardType < 1 || idCardType > 6) return "";

		AES aes = new AES("CBC", "PKCS7Padding",
				// 密钥，可以自定义
				SecurityConstants.ID_CARD_ENCRYPT_KEY[idCardType].getBytes(),
				// iv加盐，按照实际需求添加
				SecurityConstants.ID_CARD_ENCRYPT_IV.getBytes());

		return aes.encryptBase64(idCard);
	}

	/**
	 * 证件号解密
	 *
	 * @param idCardType 证件号类型
	 * @param idCardEnc  证件号密文
	 * @return String 证件号明文
	 */
	public static String idCardDecrypt(int idCardType, String idCardEnc) {
		if (idCardType < 1 || idCardType > 6) return "";

		AES aes = new AES("CBC", "PKCS7Padding",
				// 密钥，可以自定义
				SecurityConstants.ID_CARD_ENCRYPT_KEY[idCardType].getBytes(),
				// iv加盐，按照实际需求添加
				SecurityConstants.ID_CARD_ENCRYPT_IV.getBytes());

		return aes.decryptStr(idCardEnc);
	}
}
